import { useEffect, useState } from 'react';
import { Modal } from 'antd';
import BizIcon from '@/components/BizIcon';
import { FormDataStore, currentUrlIsPrevUrl } from '@/utils/formHelper';
import { pickBy, isEqual, identity, isEmpty, debounce } from 'lodash';
import events from '@/utils/eventBus';

const { confirm } = Modal;

/**
 * @description: 表单暂存功能：本地有缓存数据时，第一次进入页面弹窗提示是否加载缓存数据；表单数据变化的时候自动存入缓存里
 * @param {*}: form: 表单对象；action: 表单是新增或者编辑，取值'create'||other；id: 编辑或其他方式；key: 缓存的页面key值
 * @return {*}: formData: 缓存的表单数据；status: 自动保存提示信息状态；isFirstTimeToPage: 是否第一次进入页面
 */
const useFormStorage = ({ form, action, id, key }) => {
    // 缓存的表单数据
    const [formData, setFormData] = useState(null);
    // 自动保存提示信息状态: 1、初始状态：最近保存：刚刚；2、保存中； 3、保存成功：14:02；4、上次保存：2021-04-16 14:02
    const [status, setStatus] = useState(1);
    // 是否第一次进入页面
    const [isFirstTimeToPage, setIsFirstTimeToPage] = useState(false);
    // 最近保存的时间
    const [saveTime, setSaveTime] = useState();
    // 获取表单数据
    const formFieldsValue = form.getFieldsValue();
    const isCreate = action === 'create';

    useEffect(() => {
        const confirmInstance = document.querySelector('.load-form-data');
        // 判断是否有缓存的数据
        const initialStorage = FormDataStore({ type: 'get', key, action, id });

        if (!isEmpty(initialStorage) && !confirmInstance && !currentUrlIsPrevUrl()) {
            // 判断第一次进入页面，加载弹窗提示
            confirm({
                className: 'load-form-data',
                title: '继续编辑上次保存的草稿？',
                content: '',
                // eslint-disable-next-line react/react-in-jsx-scope
                icon: <BizIcon type="nitificationIcon" />,
                cancelText: '清除草稿',
                okText: '继续编辑',
                onOk() {
                    setFormData(initialStorage);
                    // 上次保存
                    setStatus(4);
                    const lastSaveTime = FormDataStore({
                        type: 'get',
                        key,
                        id: `${isCreate ? 'create' : id}.saveTime`
                    });
                    // 上次保存时间
                    setSaveTime(lastSaveTime);
                },
                onCancel() {
                    // 清空表单数据
                    FormDataStore({ type: 'remove', key, action, id });
                    // 清空最后一次保存的时间
                    FormDataStore({ type: 'remove', key, id: `${isCreate ? 'create' : id}.saveTime` });
                }
            });
        }
        // 获取是否有第一次进入页面的缓存字段
        const hasFirstTimeToPageField = FormDataStore({
            type: 'get',
            key,
            id: 'isFirstTimeToPage'
        });
        // 没有缓存的话就是第一次进入页面
        if (!hasFirstTimeToPageField) {
            setIsFirstTimeToPage(true);
            FormDataStore({ type: 'set', key, value: true, id: 'isFirstTimeToPage' });
        }

        // 发布订阅关闭提示
        events.addListener('closeTooltip', () => {
            setIsFirstTimeToPage(false);
        });
    }, [action, id, isCreate, key]);

    // 编辑表单，当表单数据有变化的情况下，更新缓存数据
    useEffect(() => {
        const formDataStore = FormDataStore({ type: 'get', key, action, id });
        // 通过获取当前触发的焦点元素是表单下的元素时，才缓存数据，这点很重要！！！
        let formNodeList = document.querySelectorAll('.ant-form');
        let isActiveElementBelongForm = false;
        if (formNodeList) {
            formNodeList = Array.from(formNodeList) || [];
            isActiveElementBelongForm = formNodeList.filter(item => item?.contains(document.activeElement)).length;
            if (isActiveElementBelongForm) {
                if (!isEqual(pickBy(formDataStore, identity), pickBy(formFieldsValue, identity))) {
                    FormDataStore({ type: 'set', key, value: formFieldsValue, action, id });
                    // 保存中...
                    setStatus(2);
                    // 保存当前时间，并存到缓存里
                    setSaveTime(Date.now());

                    FormDataStore({ type: 'set', key, value: Date.now(), id: `${isCreate ? 'create' : id}.saveTime` });
                    // 保存成功，这里有坑！！！暂时无解...
                    debounce(() => {
                        setStatus(3);
                    }, 500)();
                }
            }
        }
    }, [action, formFieldsValue, id, isCreate, key]);

    return {
        formData,
        status,
        isFirstTimeToPage,
        saveTime
    };
};

export default useFormStorage;
